/**
 * 
 */
package hu.gbalage.owl.editor.items.classes;

import org.eclipse.jface.viewers.ISelectionChangedListener;
import org.eclipse.jface.viewers.ITreeSelection;
import org.eclipse.jface.viewers.SelectionChangedEvent;
import org.eclipse.jface.viewers.TreeViewer;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.RGB;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Tree;
import org.semanticweb.owl.model.OWLEntity;

import hu.gbalage.owl.editor.IOWLEditorItem;
import hu.gbalage.owl.editor.OWLEditorManager;
import hu.gbalage.owl.editor.TabManager;

/**
 * @author balage
 *
 */
public class ClassHierarchyItem implements IOWLEditorItem {

	Tree tree;
	
	TreeViewer treeviewer;
	
	/* (non-Javadoc)
	 * @see hu.gbalage.owl.editor.IOWLEditorItem#getColor()
	 */
	public RGB getColor() {
		return new RGB(50,150,255);
	}

	/* (non-Javadoc)
	 * @see hu.gbalage.owl.editor.IOWLEditorItem#getTitle()
	 */
	public String getTitle() {
		return "Class Hierarchy";
	}
	
	/* (non-Javadoc)
	 * @see hu.gbalage.owl.editor.IOWLEditorItem#init(org.eclipse.swt.widgets.Composite, hu.gbalage.owl.editor.OWLEditorManager)
	 */
	public void init(Composite parent, OWLEditorManager manager,final TabManager tabManager) {
		
		treeviewer = new TreeViewer(parent,SWT.NONE);
		
		parent.setLayout(new FillLayout());
		
		treeviewer.setContentProvider(new ClassHierarchyTreeContentProvider());
		treeviewer.setLabelProvider(new ClassLabelProvider());
		treeviewer.setInput(manager);
		treeviewer.refresh();
		
		treeviewer.addSelectionChangedListener(new ISelectionChangedListener(){
			public void selectionChanged(SelectionChangedEvent event) {
				ITreeSelection selection = (ITreeSelection)event.getSelection();
				if (!selection.isEmpty())
					tabManager.selectEntity((OWLEntity)selection.getFirstElement());
			}
		});
	}
	
	/*
	 * tree = new Tree(parent,SWT.NONE);
		
		OWLOntology o = manager.getOntology();
		
		OWLClass thing = manager.getThing();
		TreeItem thingitem = new TreeItem(tree,SWT.NONE);
		thingitem.setText("Thing");
		thingitem.setData(thing);
	
		Map<OWLClass, Set<TreeItem>> treeitems = new HashMap<OWLClass, Set<TreeItem>>();
		treeitems.put(thing, new HashSet<TreeItem>());
		treeitems.get(thing).add(thingitem);
		
		Set<OWLClass> clazzes = new HashSet<OWLClass>(o.getReferencedClasses());
		clazzes.remove(thing);
		
		Map<OWLClass, Set<OWLClass>> superclasses = new HashMap<OWLClass, Set<OWLClass>>();
		
		//fill superclasses
		for(OWLClass clazz : clazzes){
			Set<OWLClass> supc = new HashSet<OWLClass>();
			superclasses.put(clazz, supc);
			for(OWLSubClassAxiom a : o.getSubClassAxiomsForLHS(clazz)){
				OWLDescription d = a.getSuperClass();
				if (!d.isAnonymous())
					supc.add(d.asOWLClass());
			}
			for(OWLEquivalentClassesAxiom a : o.getEquivalentClassesAxioms(clazz)){
				//System.out.println(clazz+" equivalent with: ");
				for(OWLDescription d : a.getDescriptions()){
					if (d instanceof OWLObjectIntersectionOf){
						OWLObjectIntersectionOf io = (OWLObjectIntersectionOf)d;
						for(OWLDescription u : io.getOperands()){
							if(!u.isAnonymous()) supc.add(u.asOWLClass());
						}
					}
					//System.out.println(d.toString()+" ("+d.getClass()+")");
				}
			}
		}
		
		//System.out.println("Start algorythm");
		while(!clazzes.isEmpty()){
			Iterator<OWLClass> iterator = clazzes.iterator();
			boolean caninsert = false;
			while(iterator.hasNext() && !caninsert){
				OWLClass clazz = iterator.next();
				//System.out.println("Check "+clazz.getURI());
				
				//we can insert this class only if 
				//all of the super classes are inserted before
				caninsert = true;
				for(OWLClass sup : superclasses.get(clazz)){
					//System.out.println("Parent: "+sup.toString());
					if (clazzes.contains(sup)){
						caninsert = false;
						//System.out.println("Not inserted!");
					}
				}
				
				if (caninsert){
					//System.out.println("inserting "+clazz.toString());
					treeitems.put(clazz, new HashSet<TreeItem>());
					if (superclasses.get(clazz).isEmpty()){
						TreeItem item = new TreeItem(thingitem,SWT.NONE);
						item.setText(clazz.getURI().getFragment());
						item.setData(clazz);
						treeitems.get(clazz).add(item);
					}else
					for(OWLClass sup : superclasses.get(clazz))
						for(TreeItem parentitem : treeitems.get(sup)){
							TreeItem item = new TreeItem(parentitem,SWT.NONE);
							item.setText(clazz.getURI().getFragment());
							item.setData(clazz);
							treeitems.get(clazz).add(item);
						}
					iterator.remove();
				}
			}
			if (!caninsert){
				System.err.println("Can't insert any remaining classes:");
				for(OWLClass c : clazzes){
					System.err.println(c.getURI().toString());
				}
				clazzes.clear();
			}
		}
		
		tree.addSelectionListener(new SelectionAdapter(){
			@Override
			public void widgetSelected(SelectionEvent e) {
				TreeItem[] items = tree.getSelection();
				if (items.length != 1) return;
				tabManager.selectEntity((OWLClass)items[0].getData());
			}
		});
		
		parent.layout();
	 */
	
}
